<?php

namespace app\components;

use app\utils\BaseUtils;
use yii;
use yii\db\ActiveRecord;
use yii\data\ActiveDataProvider;
use yii\helpers\Html;

class BaseActiveRecord extends ActiveRecord {

    public $pageSize = 15;
    public $sortAttributes = ['id'];
    public $defaultOrder = ['id' => SORT_DESC];
    public static $statusLabels = [];
    public static $statusColors = [];

    const STATUS_NO = 0;
    const STATUS_YES = 1;

    const SEX_BOX = 1;
    const SEX_GIRL = 2;

    public static $sexLabels = [
        self::SEX_BOX => '男',
        self::SEX_GIRL => '女',
    ];

    public function search($params) {
        $query = static::find();

        $dataProvider = new ActiveDataProvider([
            'query' => $query,
            'sort' => ['attributes' => $this->sortAttributes, 'defaultOrder' => $this->defaultOrder],
            'pagination' => $this->pageSize === FALSE ? FALSE : ['defaultPageSize' => $this->pageSize],
        ]);

        if (empty($params)) {
            return $dataProvider;
        }

        $attributes = [];
        foreach ($params as $k => $v) {
            if ($this->hasAttribute($k)) {
                $attributes[$k] = $v;
            }
        }

        if ($this->load($attributes, '') && !$this->validate($attributes)) {
            return $dataProvider;
        }

        if (!empty($attributes)) {
            foreach ($attributes as $attribute => $value) {
                $query->andFilterWhere([$attribute => $value]);
                //$query->andFilterWhere(['like', $attribute, $this->$attribute]);
            }
        }

        //$query->andFilterWhere(['ctime' => $this->ctime]);
        return $dataProvider;
    }

    public function getError() {
        return current($this->getFirstErrors());
    }

    public function beforeSave($insert) {
        if ($this->hasAttribute('ctime') && $insert && empty($this->getAttribute('ctime'))) {
            $this->setAttribute('ctime', time());
        }
        if ($this->hasAttribute('utime') && !$insert && empty($this->getAttribute('utime'))) {
            $this->setAttribute('utime', time());
        }
        return parent::beforeSave($insert);
    }

    public function save($runValidation = TRUE, $attributeNames = NULL, $toArray = FALSE, $msg = '') {
        if (!parent::save($runValidation, $attributeNames)) {
            return self::retErr($this->getError(), 1, $this->attributes);
        }
        return self::retOK(TRUE === $toArray ? $this->toArray() : [], $msg);
    }

    public function delete() {
        return parent::delete() ? self::retOK() : self::retErr($this->getError());
    }

    public static function retErr($msg = '', $code = 1, $data = []) {
        if (is_array($msg)) {
            $msg = yii\helpers\Json::encode($msg);
        }
        return ['code' => $code, 'msg' => $msg, 'data' => $data];
    }

    public static function retOK($data = [], $msg = '') {
        return ['code' => 0, 'data' => $data, 'msg' => $msg];
    }

    public function setDefault() {
        $model = static::findOne(['is_default' => static::STATUS_YES]);
        if ($model) {
            $model->setAttribute('is_default', static::STATUS_NO);
            $model->save();
        }

        $this->setAttribute('is_default', static::STATUS_YES);
        return $this->save();
    }

    public function _statusName($statusLabels = NULL, $field = 'status') {
        $v = $this->getAttribute($field);
        if (NULL === $statusLabels) {
            $statusLabels = static::$statusLabels;
        }
        return isset($statusLabels[$v]) ? $statusLabels[$v] : '';
    }

    public function _statusLabel($statusLabels = NULL, $field = 'status') {
        $name = $this->_statusName($statusLabels, $field);
        $style = $this->_statusName(static::$statusColors, $field);
        if (empty($style)) {
            $style = 'info';
        }
        $options = ['class' => "label label-{$style}"];
        return Html::tag('span', $name, $options);
    }

    public function _IsStatusNo($field = 'status') {
        $v = intval($this->getAttribute($field));
        return $v === intval(static::STATUS_NO);
    }

    public function getIsStatusNo() {
        $v = intval($this->getAttribute('status'));
        return $v === intval(static::STATUS_NO);
    }

    public function getAvatar() {
        return BaseUtils::getAvatar($this->getAttribute('avatar'));
    }

    public function cache($cacheId, callable $callable, $args = NULL, $_ = NULL) {
        $cacheId = sprintf($cacheId, $args, $_);
        $data = Yii::$app->cache->get($cacheId);
        if (!$data) {
            $data = call_user_func($callable);
            Yii::$app->cache->set($cacheId, $data);
        }
        return $data;
    }
}